package com.google.zxing.preview;

import android.content.Context;
import android.content.res.Resources;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Rect;
import android.graphics.drawable.BitmapDrawable;
import android.util.AttributeSet;
import android.view.View;

import com.focusai.efairy.R;
import com.focusai.efairy.utils.ScreenUtil;
import com.google.zxing.ResultPoint;
import com.google.zxing.camera.CameraManager;

import java.util.Collection;
import java.util.HashSet;

public abstract class QrCodeForegroundView extends View {
    private Paint paint;
    private Bitmap resultBitmap;
    protected Resources resources = getResources();
    private Context context;
    protected CameraManager cameraManager;
    protected abstract int getMaskColor();
    protected abstract int getResultColor();
    protected abstract int getFrameLineColor();
    protected abstract int getPointColor();
    protected abstract int getCornerWidth();
    protected abstract int getScanTextColor();
    protected abstract String  getScanText();
    protected abstract int getScanTextLeft();
    protected abstract int getScanTextSize();
    protected abstract long getInvaliteTime();
    protected abstract String getScanType();

    protected abstract int  getOpaque();
    protected abstract boolean  isSupportResultPoint();
    private Collection<ResultPoint> possibleResultPoints;
    private Collection<ResultPoint> lastPossibleResultPoints;
    private BitmapDrawable bd = (BitmapDrawable) getResources().getDrawable(R.drawable.qrcode_scan_line);
    private Bitmap bitmap;

    private static final int MIDDLE_LINE_WIDTH = 6;
    private static final int MIDDLE_LINE_PADDING = 5;

    public QrCodeForegroundView(Context context, AttributeSet attrs) {
        super(context, attrs);
        this.context=context;
        paint = new Paint();
        possibleResultPoints = new HashSet<>(5);
        if (bitmap == null) {
            bitmap = bd.getBitmap();
        }
    }

    @Override
    public void onDraw(Canvas canvas) {
        if (cameraManager == null) {
            return; // not ready yet, early draw before done configuring
        }
        Rect frame = cameraManager.getFramingRect();
        if (frame == null) {
            return;
        }

        int width = canvas.getWidth();
        int height = canvas.getHeight();

        paint.setColor(resultBitmap != null ? getResultColor() : getMaskColor());
        canvas.drawRect(0, 0, width, frame.top, paint);
        canvas.drawRect(0, frame.top, frame.left, frame.bottom , paint);
        canvas.drawRect(frame.right , frame.top, width, frame.bottom , paint);
        canvas.drawRect(0, frame.bottom , width, height, paint);

        if (resultBitmap != null) {
            paint.setAlpha(getOpaque());
            canvas.drawBitmap(resultBitmap, frame.left, frame.top, paint);
        } else {
            canvas.drawRect(frame.left, frame.top, frame.right, frame.top, paint);
            canvas.drawRect(frame.left, frame.top, frame.left , frame.bottom, paint);
            canvas.drawRect(frame.right , frame.top, frame.right, frame.bottom, paint);
            canvas.drawRect(frame.left, frame.bottom , frame.right, frame.bottom, paint);
            paint.setColor(getFrameLineColor());
            int widthBar = 1;
            canvas.drawRect(frame.left, frame.top, frame.right, frame.top + widthBar, paint);
            canvas.drawRect(frame.left, frame.top, frame.left + widthBar, frame.bottom, paint);
            canvas.drawRect(frame.left, frame.bottom - widthBar, frame.right, frame.bottom, paint);
            canvas.drawRect(frame.right - widthBar, frame.top, frame.right, frame.bottom, paint);

            drawFourCorner(canvas,frame);
            paint.setTextSize(getScanTextSize());
            paint.setTextAlign(Paint.Align.CENTER);
            paint.setColor(getScanTextColor());
            canvas.drawText(getScanText(), getScanTextLeft(),frame.bottom + ScreenUtil.dip2px(context,30), paint);
            Collection<ResultPoint> currentPossible = possibleResultPoints;
            Collection<ResultPoint> currentLast = lastPossibleResultPoints;
            if(isSupportResultPoint()){
	            if (currentPossible.isEmpty()) {
	                lastPossibleResultPoints = null;
	            } else {
	                possibleResultPoints = new HashSet<ResultPoint>(5);
	                lastPossibleResultPoints = currentPossible;
	                paint.setAlpha(getOpaque());
	                paint.setColor(getPointColor());
	                for (ResultPoint point : currentPossible) {
	                    canvas.drawCircle(frame.left + point.getX(), frame.top+ point.getY(), 6.0f, paint);
	                   }
	               }
	            if (currentLast != null) {
	                paint.setAlpha(getOpaque() / 2);
	                paint.setColor(getPointColor());
	                for (ResultPoint point : currentLast) {
	                    canvas.drawCircle(frame.left + point.getX(), frame.top + point.getY(), 3.0f, paint);
	                    }
	                }
            }
            postInvalidateDelayed(getInvaliteTime(), frame.left, frame.top, frame.right, frame.bottom);
        }
    }

    public void drawViewfinder() {
        resultBitmap = null;
        invalidate();
    }

    public void drawResultBitmap(Bitmap barcode) {
        resultBitmap = barcode;
        invalidate();
    }

    public void addPossibleResultPoint(ResultPoint point) {
        possibleResultPoints.add(point);
    }
    private void drawFourCorner(Canvas canvas, Rect frame) {
        paint.setColor(getResources().getColor(R.color.accent_fc5));

        // 左上角
        canvas.drawRect(frame.left-10, frame.top-10, frame.left + 30, frame.top, paint);
        canvas.drawRect(frame.left-10, frame.top, frame.left, frame.top + 30, paint);

        // 右上角
        canvas.drawRect(frame.right - 30, frame.top-10, frame.right, frame.top , paint);
        canvas.drawRect(frame.right, frame.top-10, frame.right+10, frame.top + 30, paint);

        // 左下角
        canvas.drawRect(frame.left, frame.bottom , frame.left + 30, frame.bottom+10, paint);
        canvas.drawRect(frame.left - 10, frame.bottom - 30, frame.left , frame.bottom+10, paint);

        // 右下角
        canvas.drawRect(frame.right - 30, frame.bottom , frame.right,frame.bottom+10, paint);
        canvas.drawRect(frame.right , frame.bottom - 30, frame.right+10,frame.bottom+10, paint);
    }

    public void setCameraManager(com.google.zxing.camera.CameraManager cameraManager) {
        this.cameraManager = cameraManager;
    }
}

